/*
    KMC Simulation
    Copyright (c) 2012 Filip Rozbořil

    This program is free software: you can redistribute it and/or modify
    it under the terms of the GNU General Public License as published by
    the Free Software Foundation, either version 3 of the License, or
    (at your option) any later version.

    This program is distributed in the hope that it will be useful,
    but WITHOUT ANY WARRANTY; without even the implied warranty of
    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
    GNU General Public License for more details.

    You should have received a copy of the GNU General Public License
    along with this program.  If not, see <http://www.gnu.org/licenses/>.
*/

#pragma once

#include "constants.h"
#include "GridField.h"
#include "Utils.h"

class GridObject
{
 	private:
 		Object::type mType;
 		GridObject() : mType(Object::None) { }
 		
 	protected:
 		GridObject(Object::type ot) : mType(ot) { }

 	public:
 		static GridObject None;
 		Object::type getType() { return mType; }	
};

class GridAtom : public GridObject
{
 	private:
		Site::type mSite;
 		Site::type mSitesAround[Direction::Count];
 		uint32_t mIndices[Direction::Count];
 		GridField mPosition;
		
	protected:
		GridAtom(Object::type ot) : GridObject(ot), mPosition(-1, -1) 
		{ 
			for(Direction::type dir = 0; dir < Direction::Count; ++dir)
			{
				mSitesAround[dir] = Site::Count;
			}
		}
 		
 	public: 
 		
 		Site::type getSite() { return mSite; }
		Site::type getSite(Direction::type dir) { return mSitesAround[dir]; }
		void setSite(Site::type site) { mSite = site; }
		void setSite(Direction::type dir, Site::type site) { mSitesAround[dir] = site; }
 		void setIndex(Direction::type dir, uint32_t i) { mIndices[dir] = i; }
 		uint32_t getIndex(Direction::type dir) { return mIndices[dir]; }
 		void setPosition(GridField& gf) { mPosition = gf; }
 		GridField& getPosition() { return mPosition; }
};

class AlAtom : public GridAtom
{
	public:
		AlAtom() : GridAtom(Object::AlAtom) { }
};

class GridDefect : public GridObject
{
 	public:
 		GridDefect() : GridObject(Object::DefectC) { }
};
